/**
 * 记账凭证 - 主界面
 * 
 * @author PSI
 * @copyright 2015 - present
 * @license GPL v3
 */
PCL.define("PSI.SLN0002.Voucher.MainForm", {
  extend: "PSI.AFX.Form.MainForm",

  config: {
    permission: null
  },

  /**
   * @override
   */
  initComponent() {
    const me = this;

    PCL.apply(me, {
      items: [{
        tbar: me.getToolbarCmp(),
        id: me.buildId(me, "panelQueryCmp"),
        region: "north",
        height: 95,
        header: false,
        collapsible: true,
        collapseMode: "mini",
        border: 0,
        layout: {
          type: "table",
          columns: 5
        },
        bodyCls: "PSI-Query-Panel",
        items: me.getQueryCmp()
      }, {
        region: "center",
        layout: "border",
        border: 0,
        ...PSI.Const.BODY_PADDING,
        items: [{
          region: "center",
          layout: "fit",
          split: true,
          border: 1,
          items: me.getMainGrid()
        }, {
          region: "south",
          layout: "border",
          height: "60%",
          split: true,
          collapsible: true,
          header: false,
          border: 0,
          items: [{
            region: "north",
            bodyStyle: "border-width:1px 1px 0px 1px",
            height: 40,
            layout: {
              type: "table",
              columns: 5
            },
            bodyPadding: 10,
            items: me.getVoucherSummaryCmp()
          }, {
            region: "center",
            layout: "fit",
            items: me.getDetailGrid()
          }, {
            region: "south",
            height: 110,
            split: true,
            border: 1,
            header: {
              height: 32,
              title: "选择分录查看附加项",
            },
            id: me.buildId(me, "panelFmtCols"),
            layout: {
              type: "table",
              columns: 4,
              tableAttrs: PSI.Const.TABLE_LAYOUT,
            },
            items: []
          }]
        }]
      }]
    });

    me.callParent(arguments);

    me.editQueryOrg = PCL.getCmp(me.buildId(me, "editQueryOrg"));
    me.editQueryPeriodYear = PCL.getCmp(me.buildId(me, "editQueryPeriodYear"));
    me.editQueryPeriodMonth = PCL.getCmp(me.buildId(me, "editQueryPeriodMonth"));
    me.editQueryVoucherStatus = PCL.getCmp(me.buildId(me, "editQueryVoucherStatus"));
    me.editQueryRef = PCL.getCmp(me.buildId(me, "editQueryRef"));
    me.editQueryCommitUser = PCL.getCmp(me.buildId(me, "editQueryCommitUser"));
    me.editQueryInputUser = PCL.getCmp(me.buildId(me, "editQueryInputUser"));

    me.panelQueryCmp = PCL.getCmp(me.buildId(me, "panelQueryCmp"));
    me.pagingToobar = PCL.getCmp(me.buildId(me, "pagingToobar"));
    me.comboCountPerPage = PCL.getCmp(me.buildId(me, "comboCountPerPage"));

    me.editSummaryRef = PCL.getCmp(me.buildId(me, "editSummaryRef"));
    me.editSummaryDT = PCL.getCmp(me.buildId(me, "editSummaryDT"));
    me.editSummaryBillNumber = PCL.getCmp(me.buildId(me, "editSummaryBillNumber"));
    me.editSummaryOrgName = PCL.getCmp(me.buildId(me, "editSummaryOrgName"));

    me.panelFmtCols = PCL.getCmp(me.buildId(me, "panelFmtCols"));

    // AFX: 查询控件input List
    me.__editorList = [
      me.editQueryOrg, me.editQueryCommitUser, me.editQueryInputUser,
      me.editQueryPeriodYear, me.editQueryPeriodMonth,
      me.editQueryRef, me.editQueryVoucherStatus,
    ];

    me._keyMapMain = PCL.create("PCL.util.KeyMap", PCL.getBody(), [{
      key: "N",
      ctrl: false,
      shift: false,
      alt: true,
      fn() {
        if (PSI.Const.msgBoxShowing) {
          return;
        }

        // 判断权限
        if (me.getPermission().add != "1") {
          return;
        }

        me._onAddVoucher.apply(me, []);
      },
      scope: me
    }, {
      key: "Q",
      ctrl: false,
      shift: false,
      alt: true,
      fn() {
        if (PSI.Const.msgBoxShowing) {
          return;
        }
        me.editQueryRef.focus();
      },
      scope: me
    }, {
      key: "H",
      ctrl: false,
      shift: false,
      alt: true,
      fn() {
        if (PSI.Const.msgBoxShowing) {
          return;
        }

        const panel = me.panelQueryCmp;
        if (panel.getCollapsed()) {
          panel.expand();
        } else {
          panel.collapse();
        };
      },
      scope: me
    },
    ]);

    me.queryCompanyList();
  },

  /**
   * @private
   */
  getToolbarCmp() {
    const me = this;

    let result = [];
    let list = [];

    // 新建
    if (me.getPermission().add == "1") {
      result.push({
        iconCls: "PSI-tb-new",
        text: "新建凭证 <span class='PSI-shortcut-DS'>Alt + N</span>",
        tooltip: me.buildTooltip("快捷键：Alt + N"),
        ...PSI.Const.BTN_STYLE,
        scope: me,
        handler: me._onAddVoucher,
      });
    }

    // 变更
    list = [];
    if (me.getPermission().edit == "1") {
      list.push({
        text: "编辑凭证",
        scope: me,
        handler: me._onEditVoucher,
        id: me.buildId(me, "buttonEdit")
      });
    }
    if (me.getPermission().del == "1") {
      list.push({
        text: "删除凭证",
        scope: me,
        handler: me._onDeleteVoucher,
        id: me.buildId(me, "buttonDelete")
      });
    }
    if (me.getPermission().discard == "1") {
      list.push({
        text: "红冲凭证",
        scope: me,
        handler: me._onDiscardVoucher,
        id: me.buildId(me, "buttonDiscard")
      });
    }
    if (list.length > 0) {
      if (result.length > 0) {
        result.push("-");
      }

      result.push({
        text: "变更",
        ...PSI.Const.BTN_STYLE,
        menu: list
      });
    }

    // 复核
    list = [];
    if (me.getPermission().commit == "1") {
      list.push({
        text: "复核凭证",
        scope: me,
        handler: me._onCommit,
        id: me.buildId(me, "buttonCommit")
      }, {
        text: "取消复核",
        scope: me,
        handler: me._onCancelCommit,
        id: me.buildId(me, "buttonCancelConfirm")
      });
    }
    if (list.length > 0) {
      if (result.length > 0) {
        result.push("-");
      }

      result.push({
        text: "复核",
        ...PSI.Const.BTN_STYLE,
        menu: list
      });
    }

    // 打印
    list = [];
    if (me.getPermission().print == "1") {
      list.push({
        text: "打印预览",
        iconCls: "PSI-button-print-preview",
        scope: me,
        handler: me._onPrintPreview
      }, {
        text: "直接打印",
        iconCls: "PSI-button-print",
        scope: me,
        handler: me._onPrint
      });
    }
    if (list.length > 0) {
      if (result.length > 0) {
        result.push("-");
      }

      result.push({
        text: "打印",
        ...PSI.Const.BTN_STYLE,
        menu: list
      });
    }

    // 维护工具
    list = [];
    if (me.getPermission().refReorder == "1") {
      list.push({
        text: "凭证断号重排",
        scope: me,
        handler: me._onVoucherRefReorder
      });
    }
    if (list.length > 0) {
      if (result.length > 0) {
        result.push("-");
      }

      result.push({
        text: "维护工具",
        ...PSI.Const.BTN_STYLE,
        menu: list
      });
    }

    // 指南
    // 关闭
    if (result.length > 0) {
      result.push("-");
    }
    result.push({
      iconCls: "PSI-tb-help",
      text: "指南",
      ...PSI.Const.BTN_STYLE,
      handler() {
        me.focus();
        window.open(me.URL("/Home/Help/index?t=voucher"));
      }
    }, "-", {
      iconCls: "PSI-tb-close",
      text: "关闭",
      ...PSI.Const.BTN_STYLE,
      handler() {
        me.focus();
        me.closeWindow();
      }
    });

    result = result.concat(me.getPagination(), me.getShortcutCmp());

    return result;
  },

  /**
   * 快捷访问
   * 
   * @private
   */
  getShortcutCmp() {
    return ["|",
      {
        cls: "PSI-Shortcut-Cmp",
        labelWidth: 0,
        emptyText: "快捷访问",
        xtype: "psi_mainmenushortcutfield",
        width: 90
      }
    ];
  },

  /**
 * 查询条件
 * 
 * @private
 */
  getQueryCmp() {
    const me = this;

    const modelName = me.buildModelName(me, "QueryOrg");
    PCL.define(modelName, {
      extend: "PCL.data.Model",
      fields: ["id", "name",
        "currentAccYear", "currentAccMonth" // 该组织机构的当前会计期间
      ]
    });

    return [{
      xtype: "container",
      height: 26,
      html: `<h2 style='margin-left:20px;margin-top:18px;color:#595959;display:inline-block'>记账凭证</h2>
                &nbsp;&nbsp;<span style='color:#8c8c8c'>凭证管理模块</span>
                <div style='float:right;display:inline-block;margin:10px 0px 0px 20px;border-left:1px solid #e5e6e8;height:40px'>&nbsp;</div>
                `
    }, {
      id: me.buildId(me, "editQueryOrg"),
      labelWidth: 70,
      width: 440,
      labelAlign: "right",
      labelSeparator: "",
      fieldLabel: "组织机构",
      margin: "5, 0, 0, 0",
      xtype: "combobox",
      queryMode: "local",
      editable: false,
      valueField: "id",
      displayField: "name",
      store: PCL.create("PCL.data.Store", {
        model: modelName,
        autoLoad: false,
        data: []
      }),
      listeners: {
        specialkey: {
          fn: me.__onEditSpecialKey,
          scope: me
        },
        change: {
          fn: me._onQueryOrgChange,
          scope: me
        },
      },
      colspan: 2,
    }, {
      id: me.buildId(me, "editQueryCommitUser"),
      labelAlign: "right",
      labelSeparator: "",
      fieldLabel: "复核人",
      margin: "5, 0, 0, 0",
      xtype: "psi_userfield",
      labelWidth: 70,
      showModal: true,
      listeners: {
        specialkey: {
          fn: me.__onEditSpecialKey,
          scope: me
        }
      }
    }, {
      id: me.buildId(me, "editQueryInputUser"),
      labelAlign: "right",
      labelSeparator: "",
      fieldLabel: "制单人",
      margin: "5, 0, 0, 0",
      xtype: "psi_userfield",
      labelWidth: 70,
      showModal: true,
      listeners: {
        specialkey: {
          fn: me.__onEditSpecialKey,
          scope: me
        }
      }
    }, { xtype: "container" }, {
      id: me.buildId(me, "editQueryPeriod"),
      labelWidth: 70,
      width: 220,
      labelAlign: "right",
      labelSeparator: "",
      fieldLabel: "会计期间",
      margin: "5, 0, 0, 0",
      xtype: "fieldcontainer",
      layout: "hbox",
      items: [
        {
          xtype: "numberfield",
          hideTrigger: true,
          allowDecimals: false,
          width: 40,
          value: (new Date()).getFullYear(),
          id: me.buildId(me, "editQueryPeriodYear"),
          listeners: {
            specialkey: {
              fn: me.__onEditSpecialKey,
              scope: me
            }
          }
        }, { xtype: "displayfield", value: "年", width: 15, }, {
          xtype: "combobox",
          width: 70,
          store: PCL.create("PCL.data.ArrayStore", {
            fields: ["id", "text"],
            data: [[1, "一月"], [2, "二月"],
            [3, "三月"], [4, "四月"],
            [5, "五月"], [6, "六月"],
            [7, "七月"], [8, "八月"],
            [9, "九月"], [10, "十月"],
            [11, "十一月"], [12, "十二月"]]
          }),
          valueField: "id",
          displayFIeld: "text",
          queryMode: "local",
          editable: false,
          value: (new Date()).getMonth() + 1,
          id: me.buildId(me, "editQueryPeriodMonth"),
          listeners: {
            specialkey: {
              fn: me.__onEditSpecialKey,
              scope: me
            }
          }
        }
      ],
    }, {
      id: me.buildId(me, "editQueryRef"),
      labelWidth: 90,
      width: 220,
      labelAlign: "right",
      labelSeparator: "",
      fieldLabel: "凭证号 <span class='PSI-shortcut-DS'>Alt + Q</span>",
      margin: "5, 0, 0, 0",
      xtype: "textfield",
      listeners: {
        specialkey: {
          fn: me.__onEditSpecialKey,
          scope: me
        }
      }
    }, {
      id: me.buildId(me, "editQueryVoucherStatus"),
      xtype: "combo",
      queryMode: "local",
      editable: false,
      valueField: "id",
      labelWidth: 70,
      labelAlign: "right",
      labelSeparator: "",
      fieldLabel: "凭证状态",
      margin: "5, 0, 0, 0",
      store: PCL.create("PCL.data.ArrayStore", {
        fields: ["id", "text"],
        data: [[-1, "全部"], [0, "待复核"], [1000, "已复核未记账"], [2000, "已记明细账"], [2000, "已记总分类账"]]
      }),
      value: -1,
      listeners: {
        specialkey: {
          fn: me.__onLastEditSpecialKey,
          scope: me
        }
      }
    }, {
      xtype: "container",
      colspan: 2,
      items: [{
        xtype: "button",
        text: "查询",
        cls: "PSI-Query-btn1",
        width: 100,
        height: 26,
        margin: "5 0 0 10",
        handler: me._onQuery,
        scope: me
      }, {
        xtype: "button",
        text: "清空查询条件",
        cls: "PSI-Query-btn2",
        width: 100,
        height: 26,
        margin: "5, 0, 0, 10",
        handler: me._onClearQuery,
        scope: me
      }, {
        xtype: "button",
        text: "隐藏工具栏 <span class='PSI-shortcut-DS'>Alt + H</span>",
        cls: "PSI-Query-btn3",
        width: 140,
        height: 26,
        iconCls: "PSI-button-hide",
        margin: "5 0 0 20",
        handler() {
          me.panelQueryCmp.collapse();
        },
        scope: me
      }]
    },];
  },

  /**
 * 分页
 * 
 * @private
 */
  getPagination() {
    const me = this;
    const store = me.getMainGrid().getStore();
    const result = ["->", {
      id: me.buildId(me, "pagingToobar"),
      xtype: "pagingtoolbar",
      cls: "PSI-Pagination",
      border: 0,
      store,
    }, "-", {
        xtype: "displayfield",
        fieldStyle: "font-size:13px",
        value: "每页显示"
      }, {
        id: me.buildId(me, "comboCountPerPage"),
        xtype: "combobox",
        cls: "PSI-Pagination",
        editable: false,
        width: 60,
        store: PCL.create("PCL.data.ArrayStore", {
          fields: ["text"],
          data: [["20"], ["50"], ["100"],
          ["300"], ["1000"]]
        }),
        value: 20,
        listeners: {
          change: {
            fn() {
              store.pageSize = me.comboCountPerPage.getValue();
              store.currentPage = 1;
              me.pagingToobar.doRefresh();
            },
            scope: me
          }
        }
      }, {
        xtype: "displayfield",
        fieldStyle: "font-size:13px",
        value: "张凭证"
      }];

    return result;
  },

  /**
   * 凭证主表
   * 
   * @private
   */
  getMainGrid() {
    const me = this;
    if (me._mainGrid) {
      return me._mainGrid;
    }

    const modelName = me.buildModelName(me, "Voucher");
    PCL.define(modelName, {
      extend: "PCL.data.Model",
      fields: ["id", "voucherStatus", "voucherStatusId", "word", "ref", "voucherDT", "confirmUserName", "confirmDT",
        "glUserName", "glDT", "glUserName2", "glDT2", "chargeUserName",
        "cashUserName", "bizUserName", "billNumber", "orgName",
        "inputUserName", "inputDT",
      ]
    });
    const store = PCL.create("PCL.data.Store", {
      autoLoad: false,
      model: modelName,
      data: [],
      pageSize: 20,
      proxy: {
        type: "ajax",
        actionMethods: {
          read: "POST"
        },
        url: me.URL("SLN0002/Voucher/voucherList"),
        reader: {
          root: 'dataList',
          totalProperty: 'totalCount'
        }
      }
    });
    store.on("beforeload", () => {
      store.proxy.extraParams = me.getQueryParam();
    });
    store.on("load", (e, records, successful) => {
      if (successful) {
        me.gotoMainGridRecord(me._lastId);
      }
    });

    me._mainGrid = PCL.create("PCL.grid.Panel", {
      cls: "PSI-FC",
      viewConfig: {
        enableTextSelection: true
      },
      border: 0,
      columnLines: true,
      columns: [{
        xtype: "rownumberer",
        text: "#",
        width: 50
      }, {
        header: "状态",
        dataIndex: "voucherStatus",
        menuDisabled: true,
        sortable: false,
        width: 100,
        renderer(value) {
          if (value == "待复核") {
            return `<span style='color:#d46b08'>${value}</span>`;
          } else if (value == "已复核未记账") {
            return `<span style='color:#237804'>${value}</span>`;
          } else {
            return value;
          }
        }
      }, {
        header: "凭证字",
        dataIndex: "word",
        width: 60,
        menuDisabled: true,
        sortable: false
      }, {
        header: "凭证号",
        dataIndex: "ref",
        width: 120,
        menuDisabled: true,
        sortable: false
      }, {
        header: "凭证日期",
        dataIndex: "voucherDT",
        width: 90,
        menuDisabled: true,
        sortable: false
      }, {
        header: "制单人",
        dataIndex: "inputUserName",
        menuDisabled: true,
        sortable: false
      }, {
        header: "制单时间",
        dataIndex: "inputDT",
        width: 150,
        menuDisabled: true,
        sortable: false
      }, {
        header: "复核人",
        dataIndex: "confirmUserName",
        menuDisabled: true,
        sortable: false
      }, {
        header: "复核时间",
        dataIndex: "confirmDT",
        width: 150,
        menuDisabled: true,
        sortable: false
      }, {
        header: "明细账记账人",
        dataIndex: "glUserName",
        menuDisabled: true,
        sortable: false
      }, {
        header: "明细账记账时间",
        dataIndex: "glDT",
        width: 150,
        menuDisabled: true,
        sortable: false
      }, {
        header: "总分类账记账人",
        dataIndex: "glUserName2",
        menuDisabled: true,
        sortable: false,
        width: 120
      }, {
        header: "总分类账记账时间",
        dataIndex: "glDT2",
        width: 150,
        menuDisabled: true,
        sortable: false
      }, {
        header: "会计主管",
        dataIndex: "chargeUserName",
        menuDisabled: true,
        sortable: false
      }, {
        header: "出纳",
        dataIndex: "cashUserName",
        menuDisabled: true,
        sortable: false
      }, {
        header: "业务责任人",
        dataIndex: "bizUserName",
        menuDisabled: true,
        sortable: false
      }, {
        header: "原始凭证数",
        dataIndex: "billNumber",
        menuDisabled: true,
        sortable: false,
        width: 90,
        tooltip: me.buildTooltip("本凭证所附原始凭证数，空白则表示没有原始凭证"),
      }, {
        header: "组织机构",
        width: 300,
        dataIndex: "orgName",
        menuDisabled: true,
        sortable: false
      }],
      listeners: {
        select: {
          fn: me._onMainGridSelect,
          scope: me
        },
        itemdblclick: {
          fn: me.getPermission().edit == "1"
            ? me._onEditVoucher
            : PCL.emptyFn,
          scope: me
        }
      },
      store: store,
    });

    return me._mainGrid;
  },

  /**
 * @private
 */
  gotoMainGridRecord(id) {
    const me = this;
    const grid = me.getMainGrid();
    grid.getSelectionModel().deselectAll();
    const store = grid.getStore();
    if (id) {
      const r = store.findExact("id", id);
      if (r != -1) {
        grid.getSelectionModel().select(r);
      } else {
        grid.getSelectionModel().select(0);
      }
    } else {
      grid.getSelectionModel().select(0);
    }
  },

  /**
   * @private
   */
  getVoucherSummaryCmp() {
    const me = this;

    const fieldProps = {
      xtype: "textfield",
      readOnly: true,
      labelSeparator: "",
      labelAlign: "right",
    };
    return [{
      xtype: "container",
      height: 22,
      html: "<span style='padding:0px;margin:0px 0px 0px -5px;border-left: 5px solid #9254de'></span>",
    }, {
      id: me.buildId(me, "editSummaryRef"),
      fieldLabel: "凭证号",
      fieldCls: "PSI-bill-summary-field",
      labelWidth: 50,
      value: "",
      ...fieldProps,
    }, {
      id: me.buildId(me, "editSummaryDT"),
      fieldLabel: "凭证日期",
      labelWidth: 90,
      value: "",
      ...fieldProps,
    }, {
      fieldLabel: "原始凭证数",
      labelAlign: "right",
      labelSeparator: "",
      labelWidth: 90,
      width: 160,
      xtype: "fieldcontainer",
      layout: "hbox",
      items: [{
        id: me.buildId(me, "editSummaryBillNumber"),
        labelWidth: 90,
        width: 50,
        xtype: "numberfield",
        readOnly: true,
        value: "",
      }, {
        xtype: "displayfield", value: "张", width: 15,
      }]
    }, {
      id: me.buildId(me, "editSummaryOrgName"),
      fieldLabel: "组织机构",
      labelWidth: 90,
      value: "",
      ...fieldProps,
    }];
  },

  /**
   * @private
   */
  resetSummaryInput() {
    const me = this;

    me.editSummaryRef.setValue("");
    me.editSummaryDT.setValue("");
    me.editSummaryBillNumber.setValue("");
    me.editSummaryOrgName.setValue("");

    me.panelFmtCols.setTitle("选择分录查看分录附加项");
  },

  /**
   * 凭证明细表 - 会计分录
   */
  getDetailGrid() {
    const me = this;
    if (me._detailGrid) {
      return me._detailGrid;
    }

    const modelName = me.buildModelName(me, "VoucherDetail");
    PCL.define(modelName, {
      extend: "PCL.data.Model",
      fields: ["id", "subject", {
        name: "debit",
        type: "float"
      }, {
          name: "credit",
          type: "float"
        }, "summary", "fmtCols"]
    });
    const store = PCL.create("PCL.data.Store", {
      autoLoad: false,
      model: modelName,
      data: []
    });

    me._detailGrid = PCL.create("PCL.grid.Panel", {
      cls: "PSI-HL",
      viewConfig: {
        enableTextSelection: true
      },
      features: [{
        ftype: "summary",
        dock: "bottom",
      }],
      border: 0,
      columnLines: true,
      columns: [PCL.create("PCL.grid.RowNumberer", {
        text: "#",
        width: 40
      }), {
        header: "科目",
        dataIndex: "subject",
        menuDisabled: true,
        sortable: false,
        width: 400,
        summaryRenderer() {
          return "<span style='color:#006d75;font-size:12px'>金额合计</span>";
        },
      }, {
        header: "借方金额",
        dataIndex: "debit",
        menuDisabled: true,
        sortable: false,
        align: "right",
        summaryType: "sum",
        width: 120,
        renderer(value) {
          return me.formatMoney(value);
        }
      }, {
        header: "贷方金额",
        dataIndex: "credit",
        menuDisabled: true,
        sortable: false,
        align: "right",
        summaryType: "sum",
        width: 120,
        renderer(value) {
          return me.formatMoney(value);
        }
      }, {
        header: "摘要",
        dataIndex: "summary",
        menuDisabled: true,
        sortable: false,
        width: 400
      }],
      store,
      listeners: {
        select: {
          fn() {
            me.createInputsFromFmtCols();
          },
          scope: me
        },
      },
    });

    return me._detailGrid;
  },

  /**
   * @private
   */
  getQueryParam() {
    const me = this;

    // 组织机构
    const result = {
      orgId: me.editQueryOrg.getValue(),
    };

    // 会计期间
    let year = me.editQueryPeriodYear.getValue();
    if (!year) {
      year = (new Date()).getFullYear();
    }
    let month = me.editQueryPeriodMonth.getValue();
    if (!month) {
      month = (new Date()).getMonth() + 1;
    }
    result.year = year;
    result.month = month;

    const ref = me.editQueryRef.getValue();
    if (ref) {
      result.ref = ref;
    }

    const status = me.editQueryVoucherStatus.getValue();
    result.status = status;

    const commitUserId = me.editQueryCommitUser.getIdValue();
    if (commitUserId) {
      result.commitUserId = commitUserId;
    }

    const inputUserId = me.editQueryInputUser.getIdValue();
    if (inputUserId) {
      result.inputUserId = inputUserId;
    }

    return result;
  },

  /**
   * @private
   */
  queryCompanyList() {
    const me = this;
    const store = me.editQueryOrg.getStore();
    const r = {
      url: me.URL("SLN0002/Voucher/companyList"),
      callback(options, success, response) {
        store.removeAll();

        if (success) {
          const data = me.decodeJSON(response.responseText);
          store.add(data);
          if (data.length > 0) {
            me.editQueryOrg.setValue(data[0]["id"]);

            const currentAccYear = data[0]["currentAccYear"];
            const currentAccMonth = parseInt(data[0]["currentAccMonth"]);
            if (currentAccYear) {
              me.editQueryPeriodYear.setValue(currentAccYear);
              me.editQueryPeriodMonth.setValue(currentAccMonth);
            }

            me.refreshMainGrid();
          }
        }
      }
    };
    me.ajax(r);
  },

  /**
   * 新建凭证
   * 
   * @private
   */
  _onAddVoucher() {
    const me = this;

    const form = PCL.create("PSI.SLN0002.Voucher.SelectOrgAndWordForm", {
      parentForm: me
    });
    form.show();
  },

  /**
   * @private
   */
  doAddVoucher(org, word, accYear, accMonth) {
    const me = this;

    const dt = new Date();
    const year = dt.getFullYear();
    const month = dt.getMonth() + 1;
    const day = dt.getDate();

    let voucherDT = "";
    if (accYear != year || accMonth != month) {
      // 当前年月不是会计期间，这种情况多半是刚开始使用的时候，在补录之前月份的凭证
      voucherDT = accYear.toString() + "-" + accMonth.toString().padStart(2, "0") + "-01";
    } else {
      voucherDT = year.toString() + "-" + month.toString().padStart(2, "0") + "-"
        + day.toString().padStart(2, "0");
    }

    const form = PCL.create("PSI.SLN0002.Voucher.EditForm", {
      parentForm: me,
      selectedOrg: org,
      selectedWord: word,
      currentVoucherDT: voucherDT,
    });
    form.show();
  },

  /**
   * 编辑凭证
   * 
   * @private
   */
  _onEditVoucher() {
    const me = this;

    const item = me.getMainGrid().getSelectionModel().getSelection();
    if (item == null || item.length != 1) {
      me.showInfo("请选择要编辑的记账凭证");
      return;
    }

    const voucher = item[0];

    const form = PCL.create("PSI.SLN0002.Voucher.EditForm", {
      parentForm: me,
      entity: voucher,
    });
    form.show();

  },

  /**
   * 删除凭证
   * 
   * @private
   */
  _onDeleteVoucher() {
    const me = this;

    const item = me.getMainGrid().getSelectionModel().getSelection();
    if (item == null || item.length != 1) {
      me.showInfo("请选择要删除的记账凭证");
      return;
    }

    const voucher = item[0];

    if (parseInt(voucher.get("voucherStatusId")) > 0) {
      me.showInfo("当前记账凭证已经复核，不能删除");
      return;
    }

    const store = me.getMainGrid().getStore();
    let index = store.findExact("id", voucher.get("id"));
    index--;
    let preIndex = null;
    const preItem = store.getAt(index);
    if (preItem) {
      preIndex = preItem.get("id");
    }

    const info = `请确认是否删除 <span style='color:red'>${voucher.get("ref")}</span> 记账凭证？`;
    const funcConfirm = () => {
      const el = PCL.getBody();
      el.mask("正在删除中...");
      const r = {
        url: me.URL("SLN0002/Voucher/deleteVoucher"),
        params: {
          id: voucher.get("id")
        },
        callback(options, success, response) {
          el.unmask();

          if (success) {
            const data = me.decodeJSON(response.responseText);
            if (data.success) {
              me.resetSummaryInput();
              me.panelFmtCols.removeAll();
              me.getDetailGrid().getStore().removeAll();

              me.refreshMainGrid(preIndex);
              me.tip("成功完成删除操作", true);
            } else {
              me.showInfo(data.msg);
            }
          } else {
            me.showInfo("网络错误");
          }
        }
      };
      me.ajax(r);
    };

    me.confirm(info, funcConfirm);
  },

  /**
   * 复核凭证
   * 
   * @private
   */
  _onCommit() {
    const me = this;

    const item = me.getMainGrid().getSelectionModel().getSelection();
    if (item == null || item.length != 1) {
      me.showInfo("请选择要复核的记账凭证");
      return;
    }

    const voucher = item[0];

    if (voucher.get("voucherStatus") != "待复核") {
      me.showInfo("当前记账凭证已经复核，不能再次复核");
      return;
    }

    const id = voucher.get("id");

    const info = `请确认是否复核 <span style='color:red'>${voucher.get("ref")}</span> 记账凭证？`;
    const funcConfirm = () => {
      const el = PCL.getBody();
      el.mask("正在复核中...");
      const r = {
        url: me.URL("SLN0002/Voucher/commitVoucher"),
        params: {
          id,
        },
        callback(options, success, response) {
          el.unmask();

          if (success) {
            const data = me.decodeJSON(response.responseText);
            if (data.success) {
              me.resetSummaryInput();
              me.panelFmtCols.removeAll();
              me.getDetailGrid().getStore().removeAll();

              me.refreshMainGrid(id);
              me.tip("成功完成复核操作", true);
            } else {
              me.showInfo(data.msg);
            }
          } else {
            me.showInfo("网络错误");
          }
        }
      };
      me.ajax(r);
    };

    me.confirm(info, funcConfirm);
  },

  /**
   * 取消复核
   * 
   * @private
   */
  _onCancelCommit() {
    const me = this;

    const item = me.getMainGrid().getSelectionModel().getSelection();
    if (item == null || item.length != 1) {
      me.showInfo("请选择要取消复核的记账凭证");
      return;
    }

    const voucher = item[0];

    const status = voucher.get("voucherStatus");
    if (status == "待复核") {
      me.showInfo("当前记账凭证尚未复核");
      return;
    }
    if (status == "已记账") {
      me.showInfo("当前记账凭证已经记账，不能被取消复核状态了");
      return;
    }

    const id = voucher.get("id");

    const info = `请确认是否取消 <span style='color:red'>${voucher.get("ref")}</span> 记账凭证的复核状态？`;
    const funcConfirm = () => {
      const el = PCL.getBody();
      el.mask("正在取消复核中...");
      const r = {
        url: me.URL("SLN0002/Voucher/cancelCommitVoucher"),
        params: {
          id,
        },
        callback(options, success, response) {
          el.unmask();

          if (success) {
            const data = me.decodeJSON(response.responseText);
            if (data.success) {
              me.resetSummaryInput();
              me.panelFmtCols.removeAll();
              me.getDetailGrid().getStore().removeAll();

              me.refreshMainGrid(id);
              me.tip("成功完成取消复核操作", true);
            } else {
              me.showInfo(data.msg);
            }
          } else {
            me.showInfo("网络错误");
          }
        }
      };
      me.ajax(r);
    };

    me.confirm(info, funcConfirm);
  },

  /**
   * 查询
   * 
   * @private
   */
  _onQuery() {
    const me = this;

    me.getMainGrid().getStore().currentPage = 1;
    me.refreshMainGrid();
  },

  /**
   * 清空查询条件
   * 
   * @private
   */
  _onClearQuery() {
    const me = this;

    me.editQueryCommitUser.clearIdValue();
    me.editQueryInputUser.clearIdValue();
    me.editQueryPeriodYear.setValue((new Date()).getFullYear());
    me.editQueryPeriodMonth.setValue((new Date()).getMonth() + 1);
    me.editQueryRef.setValue("");
    me.editQueryVoucherStatus.setValue(-1);

    me._onQuery();
  },

  /**
   * @private
   */
  _onMainGridSelect() {
    const me = this;

    me.resetSummaryInput();

    me.panelFmtCols.removeAll();

    const item = me.getMainGrid().getSelectionModel().getSelection();
    if (item == null || item.length != 1) {
      return;
    }

    const voucher = item[0];

    me.editSummaryRef.setValue(voucher.get("ref"));
    me.editSummaryDT.setValue(voucher.get("voucherDT"));
    let billNumber = voucher.get("billNumber");
    if (!billNumber) {
      billNumber = 0;
    }
    me.editSummaryBillNumber.setValue(billNumber);
    me.editSummaryOrgName.setValue(voucher.get("orgName"));

    me.refreshDetailGrid();
  },

  refreshMainGrid(id) {
    const me = this;

    me.resetSummaryInput();

    me.pagingToobar.doRefresh();

    me._lastId = id;
  },

  /**
   * @private
   */
  refreshDetailGrid(id) {
    const me = this;
    const item = me.getMainGrid().getSelectionModel().getSelection();
    if (item == null || item.length != 1) {
      return;
    }

    const voucher = item[0];

    const grid = me.getDetailGrid();
    const el = grid.getEl();
    el?.mask(PSI.Const.LOADING);
    me.ajax({
      url: me.URL("SLN0002/Voucher/voucherDetailList"),
      params: {
        id: voucher.get("id")
      },
      callback(options, success, response) {
        const store = grid.getStore();

        store.removeAll();

        if (success) {
          const data = me.decodeJSON(response.responseText);
          store.add(data);

          if (store.getCount() > 0) {
            if (id) {
              const r = store.findExact("id", id);
              if (r != -1) {
                grid.getSelectionModel().select(r);
              }
            }
          }
        }

        el?.unmask();
      }
    });
  },

  /**
   * 打印预览
   * @private
   */
  _onPrintPreview() {
    const me = this;

    me.showInfo("TODO")
  },

  /**
   * 直接打印
   * 
   * @private
   */
  _onPrint() {
    const me = this;

    me.showInfo("TODO")
  },

  /**
   * 根据账样扩展项创建凭证录入附加项
   * 
   * @private
   */
  createInputsFromFmtCols() {
    const me = this;

    me.panelFmtCols.setTitle("选择分录查看分录附加项");
    me.panelFmtCols.removeAll();

    const item = me.getDetailGrid().getSelectionModel().getSelection();
    if (item == null || item.length != 1) {
      return;
    }
    const rec = item[0];
    const fmtCols = rec.get("fmtCols");

    const n = me.getDetailGrid().getStore().indexOf(rec) + 1;

    if (!fmtCols || fmtCols.length == 0) {
      me.panelFmtCols.setTitle(`#${n}分录 - 没有附加项`);
      return;
    }

    me.panelFmtCols.setTitle(`#${n}分录 - 附加项`);

    fmtCols.forEach((col) => {
      const input = {
        value: col.value,
        xtype: "textfield",
        fieldLabel: col.caption,
        labelAlign: "right",
        labelSeparator: "",
        labelWidth: 70,
        readOnly: true,
        width: col.width,
        colspan: col.colspan,
      };

      me.panelFmtCols.add(input);
    });
  },

  /**
   * @private
   */
  _onVoucherRefReorder() {
    const me = this;

    const companyId = me.editQueryOrg.getValue();
    if (!companyId) {
      me.showInfo("请选择组织机构");
      return;
    }

    const store = me.editQueryOrg.getStore();
    const org = store.getById(companyId);
    if (!org) {
      me.showInfo("请选择组织机构");
      return;
    }
    const companyName = org.get("name");

    const voucherYear = me.editQueryPeriodYear.getValue();
    const voucherMonth = me.editQueryPeriodMonth.getValue();

    const form = PCL.create("PSI.SLN0002.Voucher.SelectPeriodForm", {
      parentForm: me,
      caption: "凭证断号重排",
      companyName,
      voucherYear,
      voucherMonth,
      okCallbackFunc: me.voucherRefReorderCallback,
      renderTo: PSI.Const.RENDER_TO(),
    });
    form.show();
  },

  /**
   * @public
   */
  voucherRefReorderCallback(year, month) {
    const me = this;

    const companyId = me.editQueryOrg.getValue();

    const el = PCL.getBody();
    el.mask("正在操作中...");
    const r = {
      url: me.URL("SLN0002/Voucher/refReorder"),
      params: {
        companyId,
        year,
        month,
      },
      callback(options, success, response) {
        el.unmask();

        if (success) {
          const data = me.decodeJSON(response.responseText);
          if (data.success) {
            me.resetSummaryInput();
            me.panelFmtCols.removeAll();
            me.getDetailGrid().getStore().removeAll();

            me.refreshMainGrid();
            me.showInfo("成功完成凭证断号重排操作");
          } else {
            me.showInfo(data.msg);
          }
        } else {
          me.showInfo("网络错误");
        }
      }
    };
    me.ajax(r);
  },

  /**
   * @public
   */
  voucherToAccDetailCallback(year, month) {
    const me = this;

    const companyId = me.editQueryOrg.getValue();

    const el = PCL.getBody();
    el.mask("正在操作中...");
    const r = {
      url: me.URL("SLN0002/Voucher/voucherToAccDetail"),
      params: {
        companyId,
        year,
        month,
      },
      callback(options, success, response) {
        el.unmask();

        if (success) {
          const data = me.decodeJSON(response.responseText);
          if (data.success) {
            me.resetSummaryInput();
            me.panelFmtCols.removeAll();
            me.getDetailGrid().getStore().removeAll();

            me.refreshMainGrid();
            me.tip("成功登记明细分类账", true);
          } else {
            me.showInfo(data.msg);
          }
        } else {
          me.showInfo("网络错误");
        }
      }
    };
    me.ajax(r);
  },

  /**
   * @private
   */
  _onQueryOrgChange() {
    const me = this;

    const companyId = me.editQueryOrg.getValue();
    const record = me.editQueryOrg.getStore().getById(companyId);

    const currentAccYear = record.get("currentAccYear");
    const currentAccMonth = parseInt(record.get("currentAccMonth"));
    if (currentAccYear) {
      me.editQueryPeriodYear.setValue(currentAccYear);
      me.editQueryPeriodMonth.setValue(currentAccMonth);
    }
  },

  /**
   * @private
   */
  _onDiscardVoucher() {
    const me = this;

    const item = me.getMainGrid().getSelectionModel().getSelection();
    if (item == null || item.length != 1) {
      me.showInfo("请选择要红冲的记账凭证");
      return;
    }

    const voucher = item[0];

    if (parseInt(voucher.get("voucherStatusId")) <= 1000) {
      me.showInfo("当前记账凭证尚未记账，无需红冲");
      return;
    }

    const info = `请确认是否红冲 <span style='color:red'>${voucher.get("ref")}</span> 记账凭证？`;
    const funcConfirm = () => {
      const el = PCL.getBody();
      el.mask("正在处理中...");
      const r = {
        url: me.URL("SLN0002/Voucher/discardVoucher"),
        params: {
          id: voucher.get("id")
        },
        callback(options, success, response) {
          el.unmask();

          if (success) {
            const data = me.decodeJSON(response.responseText);
            if (data.success) {
              me.resetSummaryInput();
              me.panelFmtCols.removeAll();
              me.getDetailGrid().getStore().removeAll();

              me.refreshMainGrid(data.id);
              me.tip("成功完成红冲操作", true);
            } else {
              me.showInfo(data.msg);
            }
          } else {
            me.showInfo("网络错误");
          }
        }
      };
      me.ajax(r);
    };

    me.confirm(info, funcConfirm);
  }
});
